package com.ruoyi.business.service.impl;

import cn.afterturn.easypoi.word.WordExportUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.ruoyi.business.domain.TMessageInfo;
import com.ruoyi.business.domain.TRegisterInfo;
import com.ruoyi.business.domain.TUserOptLog;
import com.ruoyi.business.enums.*;
import com.ruoyi.business.service.*;
import com.ruoyi.business.vo.TRegisterInfoVo;
import com.ruoyi.business.vo.TRegisterLearnVo;
import com.ruoyi.business.vo.TRegisterNoticeVo;
import com.ruoyi.business.vo.TRegisterWorkVo;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.BaseEntity;
import com.ruoyi.common.core.domain.entity.SysRole;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.ServletUtils;
import com.ruoyi.common.utils.StringUtils;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.poi.openxml4j.util.ZipSecureFile;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.springframework.stereotype.Service;
import org.springframework.util.ResourceUtils;

import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.*;

/**
 * @author Tellsea
 * @date 2024/2/5
 */
@Slf4j
@Service
@AllArgsConstructor
public class TRegisterPersonServiceImpl implements ITRegisterPersonService {

    private final ITRegisterInfoService registerInfoService;
    private final ITMessageInfoService messageInfoService;
    private final ITRegisterNoticeService registerNoticeService;

    private final ITUserOptLogService tUserOptLogService;

    @Override
    public AjaxResult updateAllRead() {
        Long userId = SecurityUtils.getLoginUser().getUser().getUserId();
        messageInfoService.update(null, Wrappers.<TMessageInfo>lambdaUpdate()
                .set(TMessageInfo::getReadStatus, MessageReadStatusEnums.READ.getCode())
                .eq(TMessageInfo::getReceiveUserId, userId));
        return AjaxResult.success();
    }

    @Override
    public AjaxResult getLast() {
        Long userId = SecurityUtils.getUserId();
        TRegisterInfo registerInfo = registerInfoService.getOne(Wrappers.<TRegisterInfo>lambdaQuery()
                .eq(TRegisterInfo::getUserId, userId)
                .eq(TRegisterInfo::getNoticeStatus,NoticeStatusEnums.SUCCESS.getCode())
                .eq(TRegisterInfo::getSureStatus,SureStatusEnums.NO.getCode())
                .orderByDesc(BaseEntity::getCreateTime)
                .last("limit 1"));
        if (ObjectUtil.isEmpty(registerInfo)) {
            return AjaxResult.success();
        }
        TRegisterInfoVo registerInfoVo = registerInfoService.queryById(registerInfo.getId());
        return AjaxResult.success("查询成功", registerInfoVo);
    }

    @Override
    public AjaxResult saveSure(TRegisterNoticeVo entity) {
        entity.setSureTime(DateUtil.date());
        registerNoticeService.updateById(entity);
        registerInfoService.updateById(new TRegisterInfo().setId(entity.getRegisterId())
                .setSureStatus(SureStatusEnums.SUCCESS.getCode())
                .setAllocationStatus(AllocationStatusEnums.NO.getCode())
                .setCultureStatus(CultureStatusEnums.ING.getCode())
                .setPayStatus(PayStatusEnums.NO.getCode())
        );
        SysUser user = SecurityUtils.getLoginUser().getUser();
        List<String> roleList = new ArrayList<>();
        if(user.getRoles()!=null){
            for (SysRole role : user.getRoles()) {
                roleList.add(role.getRoleName());
            }
        }
        TUserOptLog tUserOptLog = new TUserOptLog()
                .setOptDesc("报道打卡")
                .setOptTime(entity.getSureTime())
                .setFromUserid(user.getUserId().toString())
                .setFromUsername(user.getNickName())
                .setFromRolename(StringUtils.join(roleList,","))
                .setToUserid(entity.getRegisterId().toString());
        tUserOptLogService.save(tUserOptLog);
        return AjaxResult.success();
    }

    @Override
    public void downloadApplyTemplate(Long id) {
        TRegisterInfoVo e = registerInfoService.queryById(id);
        String projectPath = System.getProperty("user.dir") + "/uploadPath";
        String date = DateUtil.format(DateUtil.date(), "yyyy/MM/dd/");
        String wordPath = projectPath + "/upload/" + date;
        try {
            String templatePath = projectPath + "/upload/template/register-apply.docx";
            // 文件路径
            String wordName = UUID.randomUUID() + "-" + e.getUserName() + ".docx";
            File wordPathFile = FileUtil.file(wordPath);
            if (!wordPathFile.exists()) {
                wordPathFile.mkdirs();
            }
            Map<String, Object> map = new HashMap<>(16);
            map.put("entity", e);
            if (!Objects.isNull(e.getGender())) {
                map.put("gender", e.getGender().intValue() == 1 ? "男" : "女");
            } else {
                map.put("gender", "");
            }
            for (TRegisterLearnVo learnVo : e.getRegisterLearnVoList()) {
                if(learnVo.getEndDate()==null){
                    learnVo.setEndDate("至今");
                }
                learnVo.setDateRange(learnVo.getStartDate() + " - " + learnVo.getEndDate());
                learnVo.setEducation(learnVo.getEducation() + "、" + learnVo.getDesignationName());
            }
            for (TRegisterWorkVo workVo : e.getRegisterWorkVoList()) {
                if(workVo.getEndDate()==null){
                    workVo.setEndDate("至今");
                }
                workVo.setDateRange(workVo.getStartDate() + " - " + workVo.getEndDate());
            }
            if(e.getRegisterLearnVoList()!=null && e.getRegisterLearnVoList().size()<2){
                int learnSize = e.getRegisterLearnVoList().size();
                for (int i = 0; i < 3 - learnSize; i++) {
                    e.getRegisterLearnVoList().add(new TRegisterLearnVo());
                }
            }
            if(e.getRegisterWorkVoList()!=null && e.getRegisterWorkVoList().size()<2){
                int workSize = e.getRegisterWorkVoList().size();
                for (int i = 0; i < 4 - workSize; i++) {
                    e.getRegisterWorkVoList().add(new TRegisterWorkVo());
                }
            }
            map.put("registerLearnVoList", e.getRegisterLearnVoList());
            map.put("registerWorkVoList", e.getRegisterWorkVoList());

            ZipSecureFile.setMinInflateRatio(0);
            XWPFDocument document = WordExportUtil.exportWord07(templatePath, map);
            FileOutputStream os = new FileOutputStream(wordPath + wordName);
            document.write(os);
            os.flush();
            os.close();

            HttpServletResponse response = ServletUtils.getResponse();
            // 创建一个新的Word文档
            String pdfFileName = UUID.randomUUID() + "-" + e.getUserName() + ".pdf";
            com.aspose.words.Document doc = new com.aspose.words.Document(Files.newInputStream(Paths.get(wordPath + wordName)));
            OutputStream pdfOutputStream = Files.newOutputStream(Paths.get(wordPath + pdfFileName));
            doc.getBuiltInDocumentProperties().setTitle(pdfFileName);
            doc.save(pdfOutputStream, com.aspose.words.SaveFormat.PDF);
            // 设置响应头
            response.setHeader("Content-Type", "application/pdf");
            // 输出PDF字节流
            Files.copy(Paths.get(wordPath + pdfFileName), response.getOutputStream());
            response.getOutputStream().flush();
//            response.setContentType("application/force-download");
//            response.addHeader("Content-Disposition", "attachment;fileName=" + wordName);
//            OutputStream out = response.getOutputStream();
//            document.write(out);
//            out.close();
//            os.flush();
//            os.close();
        } catch (Exception ex) {
            log.error(ex.getMessage(),ex);
            throw new ServiceException("文件下载异常，请联系管理员");
        }
    }
}
